<?php

namespace App\Console\Commands;

use App\Models\Freelancer;
use App\Models\FreelancerFourElementLog;
use App\Services\FourElement\FourElementVerificationResult;
use App\Services\FourElement\FourElementVerifier;
use Illuminate\Console\Command;
use Illuminate\Support\Facades\Log;

class VerifyFreelancerFourElementsCommand extends Command
{
    protected $signature = 'freelancer:verify-four-elements {freelancerId : 自由职业者ID}';

    protected $description = '对指定自由职业者执行四要素验证';

    protected FourElementVerifier $verifier;

    public function __construct(FourElementVerifier $verifier)
    {
        parent::__construct();
        $this->verifier = $verifier;
    }

    public function handle(): int
    {
        $freelancerId = (int) $this->argument('freelancerId');
        $freelancer = Freelancer::find($freelancerId);

        if (! $freelancer) {
            $this->error(sprintf('未找到自由职业者：%d', $freelancerId));
            return Command::FAILURE;
        }

        $payload = [
            'name' => $freelancer->name,
            'phone' => (string) $freelancer->phone,
            'id_card' => (string) $freelancer->id_card,
            'bank_account' => (string) $freelancer->bank_account,
        ];

        $logEntry = FreelancerFourElementLog::create([
            'freelancer_id' => $freelancer->id,
            'request_payload' => $payload,
            'response_payload' => null,
            'status' => 'processing',
            'message' => null,
        ]);

        try {
            $this->info(sprintf('开始验证自由职业者 %d (%s)', $freelancer->id, $freelancer->phone));

            $this->ensurePayloadIsComplete($payload);

            $result = $this->verifier->verify(
                $payload['name'],
                $payload['phone'],
                $payload['id_card'],
                $payload['bank_account']
            );

            $this->applyVerificationResult($freelancer, $logEntry, $result);

            $this->line($result->passed
                ? sprintf('<info>✓</info> 验证通过：%s', $result->message)
                : sprintf('<fg=yellow>✗</> 验证失败：%s', $result->message)
            );

            return $result->passed ? Command::SUCCESS : Command::FAILURE;
        } catch (\Throwable $e) {
            $message = sprintf('四要素验证异常：%s', $e->getMessage());
            $this->error($message);

            $freelancer->verification_status = Freelancer::VERIFICATION_REJECTED;
            $freelancer->save();

            $logEntry->update([
                'status' => 'error',
                'message' => $e->getMessage(),
                'response_payload' => [
                    'exception' => [
                        'message' => $e->getMessage(),
                        'file' => $e->getFile(),
                        'line' => $e->getLine(),
                    ],
                ],
            ]);

            Log::error('[FourElement] 自由职业者验证异常', [
                'freelancer_id' => $freelancer->id,
                'error' => $e->getMessage(),
                'file' => $e->getFile(),
                'line' => $e->getLine(),
            ]);

            return Command::FAILURE;
        }
    }

    protected function ensurePayloadIsComplete(array $payload): void
    {
        $missing = [];
        foreach ($payload as $key => $value) {
            if ($value === null || $value === '') {
                $missing[] = $key;
            }
        }

        if (! empty($missing)) {
            throw new \RuntimeException('缺少必要的四要素信息：' . implode(', ', $missing));
        }
    }

    protected function applyVerificationResult(Freelancer $freelancer, FreelancerFourElementLog $logEntry, FourElementVerificationResult $result): void
    {
        $freelancer->verification_status = $result->passed
            ? Freelancer::VERIFICATION_APPROVED
            : Freelancer::VERIFICATION_REJECTED;
        $freelancer->save();

        $logEntry->update([
            'status' => $result->passed ? 'passed' : 'failed',
            'message' => $result->message,
            'response_payload' => [
                'passed' => $result->passed,
                'message' => $result->message,
                'code' => $result->code,
                'context' => $result->context,
            ],
        ]);
    }
}
